Vegetation Index • Remote Sensing

TNDVI – Transformed Normalized Difference Vegetation Index

TNDVI (Transformed NDVI) is a non-linear transformation of NDVI designed to stabilize variance, linearize the relationship with vegetation parameters, and enhance contrast in medium–high vegetation cover. It is often used as a refined version of NDVI for biomass and canopy density analyses.

1. Concept & Equation of TNDVI

TNDVI is computed by applying a square-root transformation to NDVI, after adding a constant (commonly 0.5) to shift the range towards positive values. This reduces the impact of noise in low NDVI values and improves the correlation with vegetation biophysical parameters.

Core Equation

NDVI = (NIR − Red) / (NIR + Red)
TNDVI = √(NDVI + 0.5)

Where:

  • NIR: Near Infrared reflectance (e.g., 0.8 µm band)
  • Red: Red reflectance (e.g., 0.66 µm band)
Type: Vegetation Index Based on NDVI Non-linear transformation

Typical Value Ranges

TNDVI Interpretation (approx.)
< 0.5 Bare soil, urban surfaces, very sparse vegetation
0.5 – 0.7 Moderate vegetation, mixed covers, shrubs and grasslands
> 0.7 Dense and healthy vegetation (croplands, forests)

Key Applications

  • Refined vegetation monitoring where NDVI saturates
  • Biomass and canopy density analysis
  • Change detection in agricultural and forest areas
  • Complementing NDVI in statistical and modeling workflows

2. Data & Bands for TNDVI

Common Sensors & Bands

  • Sentinel-2 (ESA) – 10 m
    • Red: B4 (~665 nm)
    • NIR: B8 (~842 nm)
  • Landsat 8/9 OLI – 30 m
    • Red: B4
    • NIR: B5

Good Practice

  • Use atmospherically corrected surface reflectance products.
  • Filter out cloudy scenes using cloud masks or cloud percentage thresholds.
  • Clip to the area of interest (AOI) to reduce processing time.

Example Workflows

  • Time-series analysis of TNDVI for crop monitoring.
  • Comparing NDVI and TNDVI for dense vegetation areas.
  • Integrating TNDVI into regression models for biomass estimation.

3. Google Earth Engine code for TNDVI (Sentinel-2)

This script computes NDVI first, then applies the transformation TNDVI = sqrt(NDVI + 0.5) for a user-drawn AOI using Sentinel-2 Surface Reflectance data.


// -------------------------------------------------------
// TNDVI from Sentinel-2 Surface Reflectance
// Author: Start4IT (example template)
// -------------------------------------------------------

// 1) Define Area of Interest (AOI)
// Draw a polygon or rectangle on the map and name it "geometry" (default in GEE).
var roi = geometry;

// 2) Set time range
var startDate = '2023-01-01';
var endDate   = '2023-12-31';

// 3) Load Sentinel-2 SR collection and filter
var s2 = ee.ImageCollection('COPERNICUS/S2_SR')
  .filterBounds(roi)
  .filterDate(startDate, endDate)
  .filter(ee.Filter.lt('CLOUDY_PIXEL_PERCENTAGE', 20))
  .select(['B4','B8']);  // Red, NIR

// 4) Create a median composite and clip to AOI
var s2_median = s2.median().clip(roi);

// 5) Compute NDVI
// NDVI = (NIR - Red) / (NIR + Red)
var ndvi = s2_median.normalizedDifference(['B8','B4']).rename('NDVI');

// 6) Compute TNDVI
// TNDVI = sqrt(NDVI + 0.5)
var tndvi = ndvi.add(0.5).sqrt().rename('TNDVI');

// 7) Visualization parameters for TNDVI
var tndviVis = {
  min: 0.3,
  max: 1.0,
  palette: [
    '#440154', // low
    '#3b528b',
    '#21908c',
    '#5dc963',
    '#fde725'  // high
  ]
};

// 8) Center the map and add layers
Map.centerObject(roi, 10);
Map.addLayer(tndvi, tndviVis, 'TNDVI (Sentinel-2)', true);

// Optional: Add a true color background
var s2_rgb = ee.ImageCollection('COPERNICUS/S2_SR')
  .filterBounds(roi)
  .filterDate(startDate, endDate)
  .filter(ee.Filter.lt('CLOUDY_PIXEL_PERCENTAGE', 20))
  .select(['B4','B3','B2'])   // Red, Green, Blue
  .median()
  .clip(roi);

Map.addLayer(s2_rgb, {min:0, max:3000}, 'True Color (RGB)', false);

// 9) Export TNDVI as GeoTIFF to Google Drive
Export.image.toDrive({
  image: tndvi,
  description: 'TNDVI_Export',
  fileNamePrefix: 'TNDVI_Export',
  folder: 'GEE_TNDVI',
  region: roi,
  scale: 10,
  crs: 'EPSG:4326',
  maxPixels: 1e13
});